﻿using System;

namespace Test30.Engine
{
    public class Energy
    {
        public const int MinSpeed = 0;
        public const int NormalSpeed = 6;
        public const int MaxSpeed = 12;
        public const int ActionCost = 240;

        public static int GetGain(int speed)
        {
            return EnergyGains[speed];
        }
        public bool HasEnergy => _energy >= ActionCost;
        public EnergyTimerCollection Timers => _timers;
        public Energy(int speed)
        {
            _speed = new FixedSpeed(speed);
        }

        public Energy(ISpeed speed)
        {
            _speed = speed ?? throw new ArgumentNullException($"speed is null");
        }

        public void Randomize()
        {
            _energy = Rng.Int(ActionCost);
        }

        public void Spend()
        {
            _energy -= ActionCost;
        }

        public void Gain()
        {
            int speed = _speed.Speed;

            if (speed < MinSpeed) throw new ArgumentOutOfRangeException($"speed less than MinSpeed");
            if (speed > MaxSpeed) throw new ArgumentOutOfRangeException($"speed over than MaxSpeed");

            _energy += EnergyGains[speed];
            _timers.Gain(EnergyGains[speed]);
        }



        private class FixedSpeed : ISpeed
        {
            public int Speed { get; }
            public FixedSpeed(int speed)
            {
                Speed = speed;
            }
        }

        private static readonly int[] EnergyGains = new int[]
        {
            15,     // 1/4 normal speed
			20,     // 1/3 normal speed
            25,
            30,	    // 1/2 normal speed
            40,
            50,
            60,	    // normal speed
            80,
            100,
            120,    // 2x normal speed
            150,
            180,    // 3x normal speed
			240     // 4x normal speed
		};

        private readonly ISpeed _speed;
        private int _energy;
        private readonly EnergyTimerCollection _timers = new EnergyTimerCollection();
    }
}
